import sys
import json

import requests

from RequestBasedHueObject import RequestBasedHueObject
from utils import RGBtoHueSat

class HueLamp(RequestBasedHueObject):

    # Class to represent a Hue lamp.
    # These aren't really meant to be instantiated except by the HueBridge
    # class.  I.e.: If you want a HueLamp, you should get it via
    # HueBridge.lamps[1] or somesuch.

    READ_ONLY_ATTRIBUTES = [
            'PUT_URL',
            'GET_URL',
            'bridge',
            'id_',
            'type',
            'modelid',
            'swversion',
            'pointsymbol',
    ]

    def __init__(self, bridge, id_, attrs):

        self.setattr_('bridge', bridge, virtual=True)
        self.setattr_('id_', id_, virtual=True)
        self.setattr_('TIMEOUT', self.bridge.TIMEOUT, virtual=True)

        self.setattr_('PUT_URL', 'http://%s/api/%s/lights/%s/state' %
                        (self.bridge.IP_ADDRESS, self.bridge.KEY, self.id_),
                                virtual=True ) 
        self.setattr_('GET_URL', 'http://%s/api/%s/lights/%s' %
                        (self.bridge.IP_ADDRESS, self.bridge.KEY, self.id_,),
                                virtual=True )

        self.setattr_('color', (0, 0, 0), virtual=True)

        self.updateState()

    def __setattr__(self, attr, val):
        if not isinstance(val, tuple):
            val = (val,)

        if attr == 'color':
            if len(val) < 3:
                sys.stderr.write('You must provide at least a 3-tuple to HueLamp.color '
                                 'You may also optionally provide an additional '
                                 'data dictionary.')
            else:
                r = val[0]
                g = val[1]
                b = val[2]

                try:
                    if isinstance(val[3], dict):
                        data = val[3]
                    else:
                        data = {}
                except IndexError:
                    data = {}

                self.setColor(r, g, b, datadict=data)
        else:
            RequestBasedHueObject.__setattr__(self, attr, val)

    def updateState(self):
        result = requests.get( self.GET_URL )

        self.setattr_('type', result.json['type'], virtual=True)
        self.setattr_('modelid', result.json['modelid'], virtual=True)
        self.setattr_('swversion', result.json['swversion'], virtual=True)
        self.setattr_('pointsymbol', result.json['pointsymbol'], virtual=True)
        self.setattr_('name', result.json['name'], virtual=True)

        try:
            for key, val in attrs['state']:
                self.setattr_(key, val, virtual=True)
        except NameError:
            pass

    def setColor(self, r=0, g=0, b=0, datadict={}):
        hue, sat = RGBtoHueSat(r, g, b)

        hue = int(360 * 182.04 * hue)
        sat = int(255 * sat)

        data = {'sat': sat}
        data.update(datadict)

        tuple_ = (hue, data)

        RequestBasedHueObject.__setattr__(self, 'hue', tuple_)
        self.setattr_( 'color', (r, g, b), virtual=True )

    def off(self, datadict={}):
        datadict.update( {'on': False} )
        for key, val in datadict.iteritems():
            self.__setattr__( key, val )
